#ifndef __CAMERA_H__
#define __CAMERA_H__


#include "Vector.h"
#include <cmath>
#include <boost/smart_ptr/shared_ptr.hpp>


typedef struct s_persp
{
	s_persp() : m_fFOV(float(M_PI)),
				m_fAspectRatio(1.0f),
				m_fNearPlaneDist(1.0f),
				m_fFarPlaneDist(2.0f)
	{ }
	s_persp(const float fFOV, const float fAspectRatio, const float fNear, const float fFar) : 
				m_fFOV(fFOV),
				m_fAspectRatio(fAspectRatio),
				m_fNearPlaneDist(fNear),
				m_fFarPlaneDist(fFar)
	{ }
	s_persp(const s_persp & rhs) : 
				m_fFOV(rhs.m_fFOV),
				m_fAspectRatio(rhs.m_fAspectRatio),
				m_fNearPlaneDist(rhs.m_fNearPlaneDist),
				m_fFarPlaneDist(rhs.m_fFarPlaneDist)
	{ }

	float m_fFOV;
	float m_fAspectRatio;
	float m_fNearPlaneDist;
	float m_fFarPlaneDist;
} t_persp;

typedef struct s_view
{
	s_view() : m_vecPos(0.0f, 0.0f, 0.0f),
				m_vecRight(0.0f, 0.0f, 0.0f),
				m_vecUp(0.0f, 0.0f, 0.0f),
				m_vecLook(0.0f, 0.0f, 0.0f)
	{ }
	s_view(const Vector4& pos, const Vector4& right, const Vector4& up, const Vector4& look) :
				m_vecPos(pos),
				m_vecRight(right),
				m_vecUp(up),
				m_vecLook(look)
	{ }

	s_view(const s_view & rhs) : 
				m_vecPos(rhs.m_vecPos),
				m_vecRight(rhs.m_vecRight),
				m_vecUp(rhs.m_vecUp),
				m_vecLook(rhs.m_vecLook)
	{ }

	Vector4	m_vecPos;
	Vector4	m_vecRight;
	Vector4	m_vecUp;
	Vector4	m_vecLook;
} t_view;


typedef struct s_viewPort
{
	s_viewPort() :	m_uiX(0),
					m_uiY(0),
					m_uiWidth(0),
					m_uiHeight(0),
					m_fMinZ(0.0f),
					m_fMaxZ(0.0f)
	{ }

	s_viewPort(unsigned int uiX, unsigned int uiY, unsigned int uiWidth, unsigned int uiHeight, float fMinZ, float fMaxZ) :
					m_uiX(uiX),
					m_uiY(uiY),
					m_uiWidth(uiWidth),
					m_uiHeight(uiHeight),
					m_fMinZ(fMinZ),
					m_fMaxZ(fMaxZ)
	{ }

	s_viewPort(const s_viewPort & rhs) : 
				m_uiX(rhs.m_uiX),
				m_uiY(rhs.m_uiY),
				m_uiWidth(rhs.m_uiWidth),
				m_uiHeight(rhs.m_uiHeight),
				m_fMinZ(rhs.m_fMinZ),
				m_fMaxZ(rhs.m_fMaxZ)
	{ }

    unsigned int	m_uiX;
    unsigned int	m_uiY;
    unsigned int	m_uiWidth;
    unsigned int	m_uiHeight;
	float			m_fMinZ;
	float			m_fMaxZ;
} t_viewPort;



class CCamera
{
public:
	CCamera()
	{}

	CCamera(const t_persp& persp, const t_view& view, const t_viewPort& viewPort, unsigned int uiMeshID) : 
			m_persp(persp),
			m_view(view),
			m_viewPort(viewPort),
			m_uiMeshID(uiMeshID)
	{ }

	virtual ~CCamera()
	{}
	
	virtual void activateCamera()
	{ }


	void setView(const t_view& view)
	{
		m_view = view;
	}

	void setPerspective(const t_persp& persp)
	{
		m_persp = persp;
	}

	void setViewPort(const t_viewPort& viewp)
	{
		m_viewPort = viewp;
	}

	inline unsigned int getMeshID()
	{
		return m_uiMeshID;
	}

	inline void setMeshID(unsigned int uiMeshID)
	{
		m_uiMeshID = uiMeshID;
	}

protected:
	t_persp			m_persp;
	t_view			m_view;
	t_viewPort		m_viewPort;
	unsigned int	m_uiMeshID;

};
typedef boost::shared_ptr<CCamera> CameraPtr;

#endif // __CAMERA_H__